/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package com.invoice.model.dao;

import com.invoice.exceptions.InvoiceException;
import java.sql.SQLException;
import java.util.HashMap;
import java.util.List;
import javax.annotation.Resource;
import org.hibernate.Criteria;
import org.hibernate.HibernateException;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.criterion.Criterion;
import org.hibernate.criterion.Restrictions;

/**
 *
 * @author Lenin
 */
public abstract class DAOGenerico {

    private Class<Object> persistentClass;
    protected Session session;
    protected Transaction transaction;
    @Resource(name = "sessionFactory")
    private SessionFactory sessionFactory;

    public DAOGenerico() {
    }

    public DAOGenerico(Class<Object> persistentClass) {
        this.persistentClass = persistentClass;
//        rules = new HashMap<String, ReglaDTO>();
    }

    public Class<Object> getPersistentClass() {
        return persistentClass;
    }

    public Object add(Object object) throws InvoiceException {
        Object id;
        try {
            startSession();
            id = session.save(convertDTOtoPojo(object));
            transaction.commit();
            return id;
        } catch (Exception e) {
            rollback();
            throw new InvoiceException("Error en insercion", e);
        } finally {
            closeSession();
        }

    }

    public void update(Object object) throws InvoiceException {
        try {
            startSession();
            session.update(convertDTOtoPojo(object));
            transaction.commit();
        } catch (Exception e) {
            rollback();
            throw new InvoiceException("Error en update", e);
        } finally {
            closeSession();
        }
    }

    public void delete(Object object) throws InvoiceException {
        try {
            startSession();
            session.delete(convertDTOtoPojo(object));
            transaction.commit();
        } catch (Exception e) {
            rollback();
            throw new InvoiceException("Error en Delete", e);
        } finally {
            closeSession();
        }
    }

    public abstract Object convertDTOtoPojo(Object object);

    public abstract Object convertPojotoDTO(Object object);

    public void startSession() {
        session = HibernateUtil.getSessionFactory().getCurrentSession();
        transaction = session.beginTransaction();
    }

    public void rollback() {
        if (transaction != null) {
            transaction.rollback();
        }
    }

    public void closeSession() {
        if (session != null) {
            if (session.isOpen()) {
                session.close();
            }
        }
    }

    public <T> List<T> getAll(final Class<T> type) {
        startSession();
        final Criteria crit = session.createCriteria(type);
        return crit.list();

    }

    public Object getById(Object id) {
        throw new UnsupportedOperationException("Operacion no soportada aun");

    }

}
